/*
 * Copyright 2018 KiWiPeach.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package com.java8.demo06_stream_api;

import org.junit.Before;
import org.junit.Test;

import java.util.*;
import java.util.function.IntConsumer;
import java.util.stream.Collectors;
import java.util.stream.IntStream;
import java.util.stream.Stream;

/**
 * Create Date: 2018/04/10
 * 代码参考文档：https://www.youtube.com/watch?v=t1-YZ6bF-g0&list=PLTY_TqnIx0C24Xw7vDgpYlgo_WzjoGL_c
 * Description: java8的Stream测试
 *
 * @author kiwipeach [1099501218@qq.com]
 */
public class YouTubeStreamTest {

    /**
     * 格式化打印通用函数
     */
    private IntConsumer formatPrint = number -> System.out.print(number + " ");
    ;

    @Test
    public void 整型Stream() {
        System.out.println("1) 枚举10个数字");
        IntStream enumIntStream = IntStream.of(1, 9, 2, 4, 5, 6, 8, 7, 3, 0);
        enumIntStream.forEach(formatPrint);
        System.out.println();

        System.out.println("2) 生成10个随机数(左闭右开)");
        IntStream rangeIntStream = IntStream.range(10, 20);
        rangeIntStream.forEach(formatPrint);
        System.out.println();

        System.out.println("3) 合并Stream操作");
        // 不能合并已经中断的Stream集合，否则会报错：java.lang.IllegalStateException: stream has already been operated upon or closed
        // IntStream concatStream = IntStream.concat(enumIntStream, rangeIntStream);
        IntStream concatStream = IntStream.concat(
                IntStream.of(1, 9, 2, 4, 5, 6, 8, 7, 3, 0),
                IntStream.range(10, 20)
        );
        concatStream.forEach(formatPrint);
        System.out.println();

        System.out.println("4) 通过生产者模式generate生成(这里最好指定limit，不然生成个数太多内存可能会溢出)");
        IntStream generateIntStream = IntStream.generate(() -> new Random().nextInt()).limit(3);
        generateIntStream.forEach(formatPrint);
        System.out.println();
        System.out.println("5) 通过builder进行动态构建");
        IntStream.Builder builder = IntStream.builder();
        builder.add(100);
        builder.add(200);
        builder.add(300);
        builder.accept(400);
        IntStream buildIntStream = builder.build();
        buildIntStream.forEach(formatPrint);
        System.out.println();


    }

    @Test
    public void skipAndLimit测试() {
        System.out.println("skip,limit用法");
        IntStream enumIntStream = IntStream.of(1, 9, 2, 4, 5, 6, 8, 7, 3, 0);
        enumIntStream.skip(3).limit(3).forEach(formatPrint);
    }


    @Test
    public void 统计() {
        System.out.println("1) sum用法,取 4+5+6 的值");
        IntStream enumIntStream1 = IntStream.of(1, 9, 2, 4, 5, 6, 8, 7, 3, 0);
        int sum = enumIntStream1.skip(3).limit(3).sum();
        System.out.println("sum = " + sum);

        System.out.println("1) summaryStatistics用法");
        IntStream enumIntStream2 = IntStream.of(1, 9, 2, 4, 5, 6, 8, 7, 3, 0);
        IntSummaryStatistics intSummaryStatistics = enumIntStream2.summaryStatistics();
        System.out.println("sum = " + intSummaryStatistics.getSum());
    }

    @Test
    public void sortedAndFindFirst排序取第一个() {
        System.out.println("1) 排序后逆序然后取第一个");
        Stream stream = Stream.of(1, 9, 2, 4, 5, 6, 8, 7, 3, 0);
        stream.sorted(Comparator.reverseOrder()).findFirst().ifPresent(System.out::println);
    }

    @Test
    public void sortedAndFindFirst排序取第一个1() {
        // findAny并不是随机地选一个，如果是数据较少，串行地情况下，一般会返回第一个结果，如果是并行的情况，那就不能确保是第一个。
        System.out.println("1) 取数组的一个元素（并不会随机）");
        Stream stream = Stream.of(0,1 ,0, 2, 4, 5, 6, 777,9999,8, 7, 3, 0);
        stream.findAny().ifPresent(System.out::println);
    }


}
